home *** CD-ROM | disk | FTP | other *** search
/ Amiga Plus Special 18 / AMIGAplus Sonderheft 18 (1999)(ICP)(DE)[!].iso / PD / Spiele / lazymines / lazymines_src / highscores.c < prev    next >
C/C++ Source or Header  |  1999-01-03  |  10KB  |  321 lines

  1. /*
  2.  * highscores.c
  3.  * ============
  4.  * Handles highscores.
  5.  *
  6.  * Copyright (C) 1994-1998 Håkan L. Younes (lorens@hem.passagen.se)
  7.  */
  8.  
  9. #include <stdlib.h>
  10. #include <stdio.h>
  11. #include <string.h>
  12.  
  13. #include <proto/dos.h>
  14. #include <exec/types.h>
  15. #include <proto/exec.h>
  16. #include <proto/gadtools.h>
  17. #include <graphics/gfxmacros.h>
  18. #include <proto/graphics.h>
  19. #include <proto/intuition.h>
  20.  
  21. #include "display_globals.h"
  22. #include "requesters.h"
  23. #include "localize.h"
  24. #include "game.h"
  25. #include "highscores.h"
  26.  
  27.  
  28. #define HSMAGIC      "LZM#30HS"
  29.  
  30. #define NUM_SCORES   10
  31.  
  32.  
  33. extern struct Window  *main_win;
  34. extern APTR   vis_info;
  35.  
  36.  
  37. struct highscore {
  38.    char    name[31];
  39.    UWORD   score;
  40. };
  41.  
  42. static struct highscore   hiscores[2][3][NUM_SCORES];
  43. static BOOL    need_save = FALSE;
  44.  
  45.  
  46. static void
  47. default_scorers (
  48.    char  *name)
  49. {
  50.    int   i, j, k;
  51.    
  52.    
  53.    for (i = 0; i < 2; ++i)
  54.    {
  55.       for (j = 0; j < 3; ++j)
  56.       {
  57.          for (k = 0; k < NUM_SCORES; ++k)
  58.          {
  59.             strcpy (hiscores[i][j][k].name, name);
  60.             hiscores[i][j][k].score = 999;
  61.          }
  62.       }
  63.    }
  64. }
  65.  
  66.  
  67. void
  68. load_high_scores (
  69.    char  *default_name)
  70. {
  71.    BPTR   fh;
  72.    char   check[11];
  73.    int    i, j, k;
  74.    
  75.    
  76.    if (fh = Open ("lazymines.hiscore", MODE_OLDFILE))
  77.    {
  78.       Read (fh, check, sizeof (HSMAGIC));
  79.       if (!strcmp (check, HSMAGIC))
  80.       {
  81.          for (i = 0; i < 2; ++i)
  82.             for (j = 0; j < 3; ++j)
  83.                for (k = 0; k < NUM_SCORES; ++k)
  84.                   Read (fh, &hiscores[i][j][k], sizeof (hiscores[i][j][k]));
  85.       }
  86.       else
  87.          default_scorers (default_name);
  88.       
  89.       Close (fh);
  90.    }
  91.    else
  92.       default_scorers (default_name);
  93. }
  94.  
  95.  
  96. void
  97. save_high_scores (void)
  98. {
  99.    BPTR   fh;
  100.    int    i, j, k;
  101.    
  102.    
  103.    if (need_save)
  104.    {
  105.       if (fh = Open ("LazyMines.hiscore", MODE_NEWFILE))
  106.       {
  107.          Write (fh, HSMAGIC, sizeof (HSMAGIC));
  108.          for (i = 0; i < 2; ++i)
  109.             for (j = 0; j < 3; ++j)
  110.                for (k = 0; k < NUM_SCORES; ++k)
  111.                   Write (fh, &hiscores[i][j][k], sizeof (hiscores[i][j][k]));
  112.       
  113.          Close (fh);
  114.          SetProtection ("LazyMines.hiscore", 2);
  115.       }
  116.    }
  117. }
  118.  
  119.  
  120. UBYTE
  121. update_high_score (
  122.    UWORD   score)
  123. {
  124.    char    name[31];
  125.    BYTE    n = NUM_SCORES - 1;
  126.    UBYTE   get_name = 0;
  127.    
  128.    name[0] = '\0';
  129.    
  130.    while (n >= 0)
  131.    {
  132.       if (score <= hiscores[chosen_task][current_level - 1][n].score)
  133.       {
  134.          need_save = TRUE;
  135.          
  136.          if (n < NUM_SCORES - 1)
  137.          {
  138.             strcpy (hiscores[chosen_task][current_level - 1][n + 1].name,
  139.                     hiscores[chosen_task][current_level - 1][n].name);
  140.             hiscores[chosen_task][current_level - 1][n + 1].score =
  141.                             hiscores[chosen_task][current_level - 1][n].score;
  142.          }
  143.          
  144.          if (get_name == 0)
  145.          {
  146.             string_requester (main_win, vis_info,
  147.                               localized_string (MSG_NAME_REQTITLE),
  148.                               localized_string (MSG_NAME_GAD),
  149.                               name, 30);
  150.             get_name = n + 1;
  151.          }
  152.          else
  153.             --get_name;
  154.          
  155.          strcpy (hiscores[chosen_task][current_level - 1][n].name, name);
  156.          hiscores[chosen_task][current_level - 1][n].score = score;
  157.       }
  158.       --n;
  159.    }
  160.    
  161.    return get_name;
  162. }
  163.  
  164.  
  165. void
  166. display_high_scores (
  167.    UBYTE   highlight_no)
  168. {
  169.    struct RastPort   layout_rp;
  170.    ULONG             box_w, box_h, win_w, win_h, temp;
  171.    register UBYTE    n;
  172.    char              text_buf[38], win_title[128];
  173.    STRPTR            label;
  174.    
  175.    struct NewGadget   ng;
  176.    struct Gadget     *gad_list, *ok_gad;
  177.    struct Window     *req_win;
  178.    struct Requester   req;
  179.    BOOL               win_sleep, done = FALSE;
  180.    
  181.    
  182.    sprintf (win_title, "%s - %s (%s)",
  183.             localized_string (MSG_HIGHSCORES_REQTITLE),
  184.             localized_string (MSG_GAME_NOVICE + current_level - 1) + 2,
  185.             localized_string (MSG_SETTINGS_TASK_ALL + chosen_task) + 2);
  186.    InitRastPort (&layout_rp);
  187.    box_w = 37 * layout_rp.TxWidth + 2 * (INTERWIDTH + LINEWIDTH);
  188.    box_h = NUM_SCORES * layout_rp.TxHeight + 2 * (INTERHEIGHT + LINEHEIGHT);
  189.    temp = TextLength (&main_win->WScreen->RastPort,
  190.                       win_title, strlen (win_title)) + 24;
  191.    if (temp > box_w)
  192.       box_w = temp;
  193.    
  194.    label = localized_string (MSG_CONTINUE_GAD);
  195.    ng.ng_TextAttr = main_win->WScreen->Font;
  196.    ng.ng_VisualInfo = vis_info;
  197.    ng.ng_Width = TextLength (&main_win->WScreen->RastPort,
  198.                              label, strlen (label)) +
  199.                  INTERWIDTH + 2 * LINEWIDTH;
  200.    ng.ng_Height = main_win->WScreen->Font->ta_YSize +
  201.                   INTERHEIGHT + 2 * LINEHEIGHT;
  202.    win_w = ((box_w > ng.ng_Width) ? box_w : ng.ng_Width) + 2 * INTERWIDTH +
  203.            main_win->BorderLeft + main_win->BorderRight;
  204.    win_h = box_h + ng.ng_Height + 3 * INTERHEIGHT +
  205.            main_win->BorderTop + main_win->BorderBottom;
  206.    ng.ng_LeftEdge = (win_w - ng.ng_Width) / 2;
  207.    ng.ng_TopEdge = main_win->BorderTop + 2 * INTERHEIGHT + box_h;
  208.    ng.ng_GadgetText = label;
  209.    ng.ng_GadgetID = 0;
  210.    ng.ng_Flags = 0;
  211.    
  212.    ok_gad = CreateContext (&gad_list);
  213.    ok_gad = CreateGadget (BUTTON_KIND, ok_gad, &ng, TAG_DONE);
  214.    
  215.    if (ok_gad)
  216.    {
  217.       req_win = OpenWindowTags (NULL,
  218.                                 WA_Left, main_win->LeftEdge +
  219.                                          (main_win->Width - win_w) / 2,
  220.                                 WA_Top, main_win->TopEdge +
  221.                                         (main_win->Height - win_h) / 2,
  222.                                 WA_Width, win_w,
  223.                                 WA_Height, win_h,
  224.                                 WA_Title, win_title,
  225.                                 WA_ScreenTitle, main_win->ScreenTitle,
  226.                                 WA_PubScreen, main_win->WScreen,
  227.                                 WA_IDCMP, BUTTONIDCMP | IDCMP_REFRESHWINDOW,
  228.                                 WA_DragBar, TRUE,
  229.                                 WA_DepthGadget, TRUE,
  230.                                 WA_Activate, TRUE,
  231.                                 TAG_DONE);
  232.       if (req_win)
  233.       {
  234.          ULONG   winsig, timersig, sigmask;
  235.          struct IntuiMessage  *msg;
  236.          UWORD   dither_data[] = { 0xAAAA, 0x5555 };
  237.          
  238.          
  239.          win_sleep = window_sleep (main_win, &req);
  240.          SetAPen (req_win->RPort, gui_pens[SHINEPEN]);
  241.          SetAfPt (req_win->RPort, dither_data, 1);
  242.          RectFill (req_win->RPort, req_win->BorderLeft, req_win->BorderTop,
  243.                    req_win->Width - req_win->BorderRight - 1,
  244.                    req_win->Height - req_win->BorderBottom - 1);
  245.          SetAPen (req_win->RPort, gui_pens[BACKGROUNDPEN]);
  246.          SetAfPt (req_win->RPort, NULL, 0);
  247.          RectFill (req_win->RPort, req_win->BorderLeft + INTERWIDTH,
  248.                    req_win->BorderTop + INTERHEIGHT,
  249.                    req_win->BorderLeft + INTERWIDTH + box_w - 1,
  250.                    req_win->BorderTop + INTERHEIGHT + box_h - 1);
  251.          DrawBevelBox (req_win->RPort, req_win->BorderLeft + INTERWIDTH,
  252.                        req_win->BorderTop + INTERHEIGHT, box_w, box_h,
  253.                        GT_VisualInfo, vis_info, GTBB_Recessed, TRUE,
  254.                        TAG_DONE);
  255.          AddGList (req_win, gad_list, -1, -1, NULL);
  256.          RefreshGList (gad_list, req_win, NULL, -1);
  257.          GT_RefreshWindow (req_win, NULL);
  258.          
  259.          for (n = 0; n < NUM_SCORES; ++n)
  260.          {
  261.             SetAPen (req_win->RPort,
  262.                      gui_pens[((n + 1 == highlight_no) ? HIGHLIGHTTEXTPEN :
  263.                                                          TEXTPEN)]);
  264.             Move (req_win->RPort,
  265.                   req_win->BorderLeft + 2 * INTERWIDTH + LINEWIDTH,
  266.                   req_win->BorderTop + 2 * INTERHEIGHT + LINEHEIGHT +
  267.                   n * req_win->RPort->TxHeight + req_win->RPort->TxBaseline);
  268.             sprintf (text_buf, "%2d %s", n + 1,
  269.                      hiscores[chosen_task][current_level - 1][n].name);
  270.             Text (req_win->RPort, text_buf, strlen (text_buf));
  271.             Move (req_win->RPort,
  272.                   req_win->BorderLeft + box_w -
  273.                   LINEWIDTH - 3 * req_win->RPort->TxWidth,
  274.                   req_win->BorderTop + 2 * INTERHEIGHT + LINEHEIGHT +
  275.                   n * req_win->RPort->TxHeight + req_win->RPort->TxBaseline);
  276.             sprintf (text_buf, "%3d",
  277.                      hiscores[chosen_task][current_level - 1][n].score);
  278.             Text (req_win->RPort, text_buf, strlen (text_buf));
  279.          }
  280.          
  281.          winsig = 1L << req_win->UserPort->mp_SigBit;
  282.          timersig = timer_signal (timer_obj);
  283.          while (!done)
  284.          {
  285.             sigmask = Wait (winsig | timersig);
  286.             if (sigmask & winsig)
  287.             {
  288.                while (msg = GT_GetIMsg (req_win->UserPort))
  289.                {
  290.                   switch (msg->Class)
  291.                   {
  292.                   case IDCMP_GADGETUP:
  293.                      done = TRUE;
  294.                      break;
  295.                   case IDCMP_REFRESHWINDOW:
  296.                      GT_BeginRefresh (req_win);
  297.                      GT_EndRefresh (req_win, TRUE);
  298.                      break;
  299.                   }
  300.                   GT_ReplyIMsg (msg);
  301.                }
  302.             }
  303.             if (sigmask & timersig)
  304.             {
  305.                timer_reply (timer_obj);
  306.                if (time_on)
  307.                {
  308.                   timer_start (timer_obj, 0L, 1000000L);
  309.                   counter_update (time_counter,
  310.                                   counter_value (time_counter) + 1);
  311.                }
  312.             }
  313.          }
  314.          if (win_sleep)
  315.             window_wakeup (main_win, &req);
  316.          CloseWindow (req_win);
  317.       }
  318.       FreeGadgets (gad_list);
  319.    }
  320. }
  321.